<?php if (! defined ( 'BASEPATH' )) exit ( 'No direct script access allowed' );

class MY_Model extends CI_Model {
    var $table_name;
    var $table_fields_info;

    function __construct($tn = '', $tfi = array()) {
        parent::__construct();
        $this->load->database();
        
        $this->table_name = $tn;
        $this->table_fields_info = $tfi;
    }
    
    function __destruct() {
		$this->db->close();
    }

    /**
     * get data by id
     * @param $id
     * @return array data
     */
    function get_by_id($id, $select_key = '*') {
		$query = $this->db->query("SELECT " . $select_key . " FROM {$this->table_name} WHERE id = ?", array($id));
		$data = $query->row_array();
		if (count($data) == 1) {
			return $data[$select_key];
		} else {
			return $data;
		}
    }
    
	/**
     * get data by foreign id
     * @param $foreign_id
     * @param $select_key
     */
    function get_by_foreign_id($foreign_id, $select_key = '*') {
    	//if ($this->table_name != 'a_admin' OR $this->table_name != 'a_employee' OR $this->table_name != 's_society' OR $this->table_name != 's_teacher') { return FALSE; }
    	$tn_array = explode('_', $this->table_name);
    	$foreign_id_name = $tn_array[1] . '_id';
    	$query = $this->db->query("SELECT " . $select_key . " FROM {$this->table_name} WHERE " . $foreign_id_name . " = ?", array($foreign_id));
		$data = $query->row_array();
		if (count($data) == 1) {
			return $data[$select_key];
		} else {
			return $data;
		}
    }
    
	/**
     * get data by specified key
     * @param $key_name
     * @param $key_value
     * @param $select_key
     * @param boolean $row_exchange_FLAG
     * @return array/str data
     */
    function get_by($key_name, $key_value, $select_key = '*', $row_exchange_FLAG = FALSE) {
		$query = $this->db->query("SELECT {$select_key} FROM {$this->table_name} WHERE {$key_name} = ?", array($key_value));
		switch ($row_exchange_FLAG) {
			case TRUE:
				$data = $query->row_array();
				return ($select_key == '*') ? $data : $data[$select_key];
				break;
			case FALSE:
				$data = $query->result_array();
				
				if (!stripos($select_key, ',') && $select_key != '*') {
					if (!empty($data)) {
						foreach ($data as $v) {
							$temp[] = $v[$select_key];
						}
						return $temp;
					} else {
						return NULL;
					}
				} else {
					return $data;
				}
				break;
		}
    }

    /**
     * get all data
     * @return array data
     */
    function get_all() {
        $query = $this->db->get($this->table_name);
        return $query->result_array();
    }

    /**
     * get data count
     * @return int count
     */
    function get_count() {
        return $this->db->count_all_results($this->table_name);
    }

    /**
     * delete data by id
     * @param $id
     */
    function delete($id) {
        $this->db->where('id', $id);
        $this->db->delete($this->table_name);
    }
    
    /**
     * delete data by foreign id
     * @param $foreign_id
     */
    function delete_by_foreign_id($foreign_id) {
    	$tn_array = explode('_', $this->table_name);
    	$foreign_id_name = $tn_array[1] . '_id';
    	$this->db->where($foreign_id_name, $foreign_id);
        $this->db->delete($this->table_name);
    }
    
    /**
     * delete data by specified key
     * @param $key_name
     * @param $key_value
     */
    function delete_by($key_name, $key_value) {
    	$this->db->where($key_name, $key_value);
    	$this->db->delete($this->table_name);
    }

    /**
     * delete data by ids array
     * @param $ids
     */
    function delete_by_ids($ids) {
        foreach($ids as $v) {
            $this->db->where('id', $v);
            $this->db->delete($this->table_name);
        }
    }

    /**
     * add new data
     * @param $data
     */
    function save($data) {
        $this->db->insert($this->table_name, $data);
        return $this->db->insert_id();
    }

    /**
     * update data
     * @param $data
     */
    function update($data) {
        $this->db->where('id', $data['id']);
        $this->db->update($this->table_name, $data);
    }
    
	/**
     * update data by foreign id
     * @param $foreign_id
     */
    function update_by_foreign_id($foreign_id, $data) {
    	//$tn_array = explode('_', $this->table_name);
    	//$foreign_id_name = $tn_array[1] . '_id';
    	$foreign_id_name = 'con_id';
    	$this->db->where($foreign_id_name, $foreign_id);
        $this->db->update($this->table_name, $data);
    }
    
    /**
     * update data by specified key
     * @param $key_name
     * @param $key_value
     * @param $data
     */
    function update_by($key_name, $key_value, $data) {
    	$this->db->where($key_name, $key_value);
        $this->db->update($this->table_name, $data);
    }
    
    /**
     * get an array contains all fields, like: array(field_name => '', field_name => '', ...)
     */
    function get_fields() {
        $fields = $this->db->list_fields($this->table_name);
        $form_data = array();
        foreach ($fields as $v) {
            $form_data[$v] = "";
        }
        return $form_data;
    }
    
	/**
     * get an array contains all fields, like: array(field_name, field_name, ...)
     */
    function get_table_fields() {
        $fields = $this->db->list_fields($this->table_name);
        return $fields;
    }
    
    /**
     * set $this->table_fields_info array, like: array('common' => array('id', '...'), 'bool' => array('flag', '...'))
     */
    function set_table_fields_info() {
    	if (empty($this->table_fields_info)) {
    		$fields = $this->db->list_fields($this->table_name);
    		foreach ($fields as $v) {
    			if ($v == 'flag') {
    				$bool[] = $v;
    			} else {
    				$common[] = $v;
    			}
    		}
    		
    		$this->table_fields_info = array('common' => $common, 'bool' => $bool);
    	}
    }
    
    /**
     * General Query program
     * $condition['id'] = ?
     * $condition['...'] = ?
     * $condition['flag'] = ? TRUE means flag not delete, FALSE means delete
     * $condition['offset'] = ?
     * $condition['per_page'] = ?
     *
     * @param $condition
     *
     * @param $row_exchange_FLAG
     * Only for single result:
     * if set to TRUE, the single result will be exchanged from array([0] => '[0] => '...', [1] => '...'') to array([0] => ..., [1] => ...), else keep array([0] => '[0] => '...', [1] => '...'') without any change
     *
     * @param $count_FLAG
     * if set to TRUE, return the number of results, else return results
     *
     * @param $select_key
     * keep this param empty means select all keys, else select keys that you have specified
     */
    function search_by_condition($condition = array(), $row_exchange_FLAG = FALSE, $count_FLAG = FALSE, $select_key = '') {
    	// Set defalut value, to search without this just set $confition['...'] = '';
    	if (!isset($condition['flag'])) {
    		$condition['flag'] = TRUE;
    	}
    	
    	if ($select_key != '') {
    		$this->db->select($select_key);
    	}
    	
    	$this->set_table_fields_info();
    	
    	foreach ($this->table_fields_info as $k => $v) {
    		if ($k == 'common') {
    			foreach ($v as $v1) {
    				if (isset($condition[$v1])) {
    					$this->db->where($v1, $condition[$v1]);
    				}
    			}
    		} elseif ($k == 'bool') {
    			foreach ($v as $v1) {
    				if (isset($condition[$v1]) && !empty($condition[$v1])) {
    					$this->db->where($v1, ($condition[$v1]) ? 0 : 1);
    				}
    			}
    		}
    	}
    	
    	if (!$count_FLAG) {
    		if (isset($condition['offset'])) {
    			if (isset($condition['per_page'])) {
    				$this->db->limit($condition['per_page'], $condition['offset']);
    			} else {
    				$this->db->limit(PER_PAGE, $condition['offset']);
    			}
    		}
    	
    		$query = $this->db->get($this->table_name);
    		if ($query->num_rows() == 1) {
    			if (!$row_exchange_FLAG) {
    				return $query->result_array();
    			} else {
    				return $query->row_array();
    			}
    		} elseif ($query->num_rows() > 1) {
    			return $query->result_array();
    		} else {
    			return NULL;
    		}
    	} else {
    		$this->db->from($this->table_name);
    		return $this->db->count_all_results();
    	}
    }
}

